package com.epalmpay.service.member.impl;

import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

import javax.annotation.PostConstruct;
import javax.annotation.Resource;

import com.epalmpay.entity.profit.Profit;
import com.epalmpay.entity.profit.ProfitMemberMonth;
import com.epalmpay.enumdef.ActivityEnum;
import com.epalmpay.mapper.profit.ProfitMemberMonthMapper;
import com.epalmpay.payplat.result.PayBalanceResult;
import com.epalmpay.service.activity.ICouponUserService;
import com.epalmpay.service.activity.IRedPackageUserService;
import com.epalmpay.service.bonus.IBonusService;
import com.epalmpay.status.Rescode;
import com.epalmpay.dto.member.*;
import com.epalmpay.entity.*;
import com.epalmpay.enumdef.BizEnum;
import com.epalmpay.enumdef.CommonEnum;
import com.epalmpay.enumdef.BizEnum.UserStatus;
import com.epalmpay.mapper.*;
import com.epalmpay.payplat.*;
import com.epalmpay.util.AES;
import com.epalmpay.util.Const;
import com.epalmpay.util.DateUtil;
import com.epalmpay.util.Logger;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;

import com.epalmpay.exception.ApplicationException;
import com.epalmpay.dto.activity.CouponInDTO;
import com.epalmpay.dto.activity.RedPackageInDTO;
import com.epalmpay.dto.member.BalanceInDTO;
import com.epalmpay.dto.member.MemberConsumeOutDTO;
import com.epalmpay.dto.member.MemberInDTO;
import com.epalmpay.dto.member.MemberListOutDTO;
import com.epalmpay.dto.member.MemberOutDTO;
import com.epalmpay.dto.member.MemberTradeDetailInDTO;
import com.epalmpay.dto.member.MemberTradeDetailOutDTO;
import com.epalmpay.payplat.result.PayResult;
import com.epalmpay.service.management.ITemplateMailSendService;
import com.epalmpay.service.member.IMemberService;
import com.epalmpay.service.weixin.IWalletService;
import com.epalmpay.service.weixin.IWxApiWalletService;
import com.epalmpay.service.weixin.IWxBaseService;
import com.epalmpay.service.weixin.impl.WxService;
import com.epalmpay.usercenter.UserAuthApi;
import com.epalmpay.util.StringUtil;
import com.epalmpay.util.Tools;
import com.epalmpay.util.payplat.DateUtils;
import com.epalmpay.util.payplat.UtilFun;
import com.github.binarywang.java.emoji.EmojiConverter;

import me.chanjar.weixin.common.exception.WxErrorException;
import me.chanjar.weixin.mp.bean.result.WxMpUser;

@Service("memberService")
public class MemberServiceImpl implements IMemberService {
	@Resource
	private ActivityRoutineRegisterMapper activityRoutineRegisterMapper;

	@Resource
	private RedpackageUserMapper redpackageUserMapper;
	@Resource
	private MemberMapper memberMapper;
	@Resource
	private MemberGradeMapper memberGradeMapper;
	@Resource
	private GroupMapper groupMapper;
	@Resource
	private TradeOfflineMapper tradefflineMapper;
	@Resource
	private StatisMemberMapper statisMemberMapper;
	@Resource
	private UserbaseMapper userbaseMapper;

	@Resource
	private YsOilcardMemberMapper ysOilcardMemberMapper;

	@Resource
	private YsObdMapper ysObdMapper;
	@Resource
	private MemberCardMapper memberCardMapper;
	@Resource
	private BonusSendLogMapper bonusSendLogMapper;

	@Resource
	private TradeOfflineMapper tradeOfflineMapper;
	@Resource
	private GroupAccountMapper groupAccountMapper;

	@Resource
	private StatisMemberDayMapper statisMemberDayMapper;

	@Resource
	private IWxApiWalletService wxApiWalletServiceService;
	@Autowired
    @Lazy
	private ITemplateMailSendService templateMailSendService;
	
	@Autowired
	protected WxService wxService;
	@Autowired
	protected IWxBaseService wxBaseService;
	private EmojiConverter emojiConverter = EmojiConverter.getInstance();

	@Resource
	ActivityRoutineMapper activityRoutineMapper;
	@Resource
	ActivityBaseMapper activityBaseMapper;
	@Resource
	ActivityRoutineRuleMapper activityRoutineRuleMapper;

	@Resource
	IRedPackageUserService redPackageUserService;

	@Resource
	ICouponUserService couponUserService;
	@Resource
	IBonusService bonusService;
	
	@Resource
	private IWalletService walletService;

	@Resource
	private ProfitMapper profitMapper;

	@Resource
	private WalletMapper walletMapper;


	@Resource
	private ProfitMemberMonthMapper profitMemberMonthMapper;

	private ExecutorService exec;
	protected Logger logger = Logger.getLogger(this.getClass());

	@PostConstruct
	public void initialize() {
		exec = Executors.newSingleThreadExecutor();
	}


	@Resource
	private IMemberService memberService;

	@Override
	public Member findMemberinfo(Member member) throws Exception {
		// TODO Auto-generated method stub
		return memberMapper.queryMemberById(member.getId());
	}

	public List<MemberOutDTO> getMemberList(MemberInDTO memberInDTO, Page page) {
		Map<String, Object> param = new HashMap<String, Object>();
		param.put("groupId", memberInDTO.getGroupId());
		param.put("gradeId", memberInDTO.getGradeId());
		param.put("wxsubStaus", memberInDTO.getWxsubStaus());
		param.put("fromName", memberInDTO.getFromName());
		param.put("joinStart", memberInDTO.getJoinStart());
		param.put("joinEnd", memberInDTO.getJoinEnd());
		param.put("keyWord", memberInDTO.getKeyWord());

		List<MemberOutDTO> result = new ArrayList<MemberOutDTO>();

		int sumCount = memberMapper.selectMemberListCount(param);
		page.setTotalResult(sumCount);
		if (sumCount <= 0)
			return null;

		param.put("limit", page.getShowCount());
		param.put("start", page.getShowCount() * (page.getCurrentPage() - 1));

		List<Member> memberList = memberMapper.selectMemberList(param);

		for (Member member : memberList) {
			MemberOutDTO memberOutDTO = new MemberOutDTO();

			memberOutDTO.setId(member.getId());
			memberOutDTO.setCardNo(member.getCardNo());
			memberOutDTO.setName(member.getName());
			memberOutDTO.setPhone(member.getPhone());
			memberOutDTO.setGradeId( member.getGradeId());
			memberOutDTO.setMemberGradeName(member.getMemberGradeName());
			memberOutDTO.setWalletStatus(member.getWalletStatus());
			memberOutDTO.setConsumeAmount(Long.parseLong(member.getConsumeAmount().toString()));// 消费总额
			memberOutDTO.setWxsubStaus(member.getWxsubStaus());
			memberOutDTO.setJoinDate(member.getGmtCreate());
			memberOutDTO.setFromType(member.getFromType());
			memberOutDTO.setFromName(member.getFromName());
			memberOutDTO.setFromId(member.getFromId());
			memberOutDTO.setFromMode( member.getFromMode());
			memberOutDTO.setIccardNo(member.getIccardNo());
			memberOutDTO.setBonusAmount(Integer.parseInt((member.getBonusAmount().toString())));
			memberOutDTO.setBingObdCount(Integer.parseInt((member.getBingObdCount().toString())));
			result.add(memberOutDTO);
		}

		return result;
	}

	@Override
	public Member findMemberById(Member member) throws ApplicationException {
		Member mem = new Member();

		Calendar c = Calendar.getInstance();
		c.add(Calendar.MONTH, -1);
		SimpleDateFormat format = new SimpleDateFormat("yyyyMM");
		String time = format.format(c.getTime());
		member.setStringTime(time);
//		return memberMapper.queryMember(member);
		mem = memberMapper.queryMember(member);//这里有些关于会员统计的数据改为实时  sql 不该

		//会员推荐人数  //这里有些关于会员统计的数据改为实时  sql 不该 这方法其他地方也用了 这里就重新set
		StatisMemberDay statismMemberDay = statisMemberDayMapper.queryMemberInviteCount(member.getId());
//		mem.setAddUserCount(statismMemberDay.getInviteNumber());//推荐会员数
		mem.setRecommendUserCount(statismMemberDay.getRecommendUserCount());//推荐会员发展数
		Member m   = memberMapper.queryAddMemberNumber(member.getId());
		mem.setAddUserCount(m.getAddUserCount());//推荐会员数 实时查

		//上月推荐会员贡献返利
		Profit prifit = profitMapper.LastMonthProfit(member.getId());
		mem.setRecommendProfit(prifit.getDevelopeProfit());
		//上月推荐会员发展会员返利
		ProfitMemberMonth profitMemberMonth = profitMemberMonthMapper.queryLastMonthProfit(member.getId(),time);
		if(profitMemberMonth !=null){
			mem.setInviteBackAmount(profitMemberMonth.getRecommendProfit());
		}else{
			mem.setInviteBackAmount(0);
		}

		//本月推荐会员贡献返利
		Profit prifit2 = profitMapper.thisMonthProfit(member.getId());
		mem.setThisDevelopeProfit(prifit2.getDevelopeProfit());


//		//查询钱包
		// 或看钱包状态是否开通
		if(mem.getWalletStatus()==1){
			Wallet wallet=walletService.selectwallet(mem.getVirtualCard(), mem.getPayGroupCode(), mem.getUserId());
			mem.setFreezeBalance(wallet.getCanFreezeBalance());
			mem.setLockBalance(wallet.getCanBalanceLocked());
			mem.setWalletBalance(wallet.getCanBalance()+wallet.getNocanBalance());
		}else{
			mem.setFreezeBalance(0);
			mem.setLockBalance(0);
			mem.setWalletBalance(0);
		}



		return mem;
	}

	@Override
	public Member findById(Member member) {
		return memberMapper.findById(member.getId());

	}

	@Override
	public Member findMemberDetailById(Member member) {
		return memberMapper.findMemberDetailById(member.getId());
	}

	@Override
	public List<MemberCard> queryMemberCardList(MemberInDTO memberInDTO) {
		Map<String, Object> param = new HashMap<String, Object>();
		param.put("memberId", memberInDTO.getId());
		param.put("cardStatus", BizEnum.CardStatus.Verified.getType());

		List<MemberCard> result = new ArrayList<MemberCard>();

		int sumCount = memberCardMapper.selectMemberCardCount(param);
		if (sumCount <= 0)
			return result;
		List<Map<String, Object>> memberCardList = memberCardMapper.selectMemberCardList(param);

		for (Map<String, Object> memberCards : memberCardList) {
			MemberCard membercard = new MemberCard();

			membercard.setCardNum((String) memberCards.get("card_num"));
			membercard.setIssuerBankName((String) memberCards.get("issuer_bank_name"));
			membercard.setIdName((String) memberCards.get("id_name"));
			membercard.setCardType((int) memberCards.get("card_type"));

			result.add(membercard);
		}

		return result;
	}

	@Override
	public List<YsOilcardMember> queryOilcardMember(MemberInDTO memberInDTO) throws Exception {
		Map<String, Object> param = new HashMap<String, Object>();
		param.put("memberId", memberInDTO.getId());

		List<YsOilcardMember> result = new ArrayList<YsOilcardMember>();

		int sumCount = ysOilcardMemberMapper.selectOilcardMemberCount(param);
		if (sumCount <= 0)
			return result;
		List<Map<String, Object>> oilcardMemberList = ysOilcardMemberMapper.selectOilcardMemberList(param);

		for (Map<String, Object> oilcardMember : oilcardMemberList) {
			YsOilcardMember ysOilcardMember = new YsOilcardMember();

			ysOilcardMember.setId((Long) oilcardMember.get("id"));
			ysOilcardMember.setOilcardNumber((String) oilcardMember.get("oilcard_number"));
			ysOilcardMember.setOilcardName((String) oilcardMember.get("oilcard_name"));
			ysOilcardMember.setOilcardPhone((String) oilcardMember.get("oilcard_phone"));
			ysOilcardMember.setOilcardType((String) oilcardMember.get("oilcard_type"));

			result.add(ysOilcardMember);
		}

		return result;
	}

	/**
	 * 查询账户余额
	 */
	@Override
	public MemberOutDTO queryAmount(MemberInDTO memberInDTO) throws ApplicationException {
		Member member = memberMapper.queryGroup(memberInDTO.getId());
        MemberOutDTO memberOutDTO = null;
        if(member!= null) {
			if (member.getWalletStatus() == 1) {//已开通钱包
				Wallet wallet = walletService.selectwallet(member.getVirtualCard(), member.getPayGroupCode(), member.getUserId());
				memberOutDTO = new MemberOutDTO();
				memberOutDTO.setCurBal(wallet.getCanBalance() + "");
				memberOutDTO.setCurBalB(wallet.getNocanBalance() + "");
				memberOutDTO.setLockBal((wallet.getCanBalanceLocked() + wallet.getCanFreezeBalance()) + "");
				memberOutDTO.setLockBalB((wallet.getNocanBalanceLocked() + wallet.getNocanFreezeBalance()) + "");
				memberOutDTO.setPhone(member.getPhone());
				memberOutDTO.setVirtualCard(member.getVirtualCard());
			} else if (member.getWalletStatus() == 0) {//未开通钱包
			}
		}
        return memberOutDTO;
	}

	/**
	 * 重置支付密码
	 */
	@Override
	public Member reSet(MemberInDTO memberInDTO,String rootHomeUrl) throws Exception {
		Member member = memberMapper.reSetById(memberInDTO.getId());
		String sysTraceNum = StringUtil.getRandNumberStr(12);// 交易流水号12位
		String groupId = member.getPayGroupCode();
		String newPwd = "000000";
		SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyyMMddhhmmss");
		Date date = new Date();
		String str = simpleDateFormat.format(date);
		String orgTranDateTime = str;
		member.setId(memberInDTO.getId());
		member.setTradePassword(AES.AESEncode(Const.AceKey, "000000"));
		member.setGmtModified(new Date());
		memberMapper.updateByPrimaryKeySelective(member);
		FindbackPayPwd payUpdateRestPwd = FindbackPayPwd.initialize(member.getVirtualCard(), newPwd, groupId, sysTraceNum, orgTranDateTime, "000000", "000000");
		PayResult payResult = IPayAPI.findbackAccountPayPwd(payUpdateRestPwd);
		if (!PayResult.SUCCESS.equals(payResult.getRespCode())) {
			throw new Exception(payResult.getRespCode() + "#" + payResult.getMsgTxt());
		}
		try {
			templateMailSendService.sendMemberTemplate(member.getId(), BizEnum.WebTemplateType.template14.getType(), rootHomeUrl, "支付");
		} catch (Exception e) {
			logger.info("模板消息发送失败" + e);
		}
		return member;
	}

	@Override
	public void editMember(Member members) throws ApplicationException {
		memberMapper.updateByPrimaryKeySelective(members);

		// 同步支付平台 开通钱包的要同步

		Member member = memberMapper.queryGroup(members.getId());
		if (member.getWalletStatus() == 1) {

			String UserId = member.getVirtualCard();
			String GroupId = member.getPayGroupCode();
			String CustomerName = members.getName();
			String MobilePhone = member.getPhone();
			String OrgTranDateTime = DateUtils.getDateTimeString("yyyyMMddHHmmss");
			String Email = member.getName();
			String CertNo = member.getIdNo();

			PayUpdateData payUserAccounts = PayUpdateData.initialize(GroupId, UserId, CustomerName, MobilePhone, CertNo, OrgTranDateTime, Email, null, "01",
					null);// 01表示用户正常 00表示用户禁用
			PayResult payResult = IPayAPI.updateAccountData(payUserAccounts);
			if (!PayResult.SUCCESS.equals(payResult.getRespCode())) {
				throw new ApplicationException(Rescode.FAIL, payResult.getRespCode() + "#" + payResult.getMsgTxt());
			}

		}

	}

	@Override
	public List<MemberOutDTO> findMemberGradeById(Long id) {
		List<MemberOutDTO> result = new ArrayList<MemberOutDTO>();

		List<Map<String, Object>> memberList = memberMapper.findMemberGradeById(id);

		for (Map<String, Object> member : memberList) {
			MemberOutDTO memberOutDTO = new MemberOutDTO();
			memberOutDTO.setMemberGradeName(member.get("member_grade_name").toString());
			result.add(memberOutDTO);
		}
		return result;
	}

	@Override
	public Member findGradeMemberById(Member member) {
		return memberMapper.findGradeMemberById(member);
	}

	@Override
	public Member findPasswordById(Member member) {
		return memberMapper.findPasswordById(member);
	}

	@Override
	public void updateMember(Member member) {
		memberMapper.updateByPrimaryKeySelective(member);

	}

	@Override
	public void updateMemberLoginPassword(Member member) {

		memberMapper.updateByPrimaryKeySelective(member);

	}

	@Override
	public List<Long> getMembers(RedPackageInDTO redPackageInDTO) {
		return memberMapper.getMembers(redPackageInDTO);
	}

	@Override
	public List<Long> getMembersByCoupon(CouponInDTO couponInDTO) {
		return memberMapper.getMembersByCoupon(couponInDTO);
	}

	@Override
	public MemberListOutDTO queryTradeDetail(MemberTradeDetailInDTO memberTradeDetailInDTO, Page page) throws ApplicationException {
		MemberListOutDTO memberListOutDTO = new MemberListOutDTO();

		Map<String, Object> param = new HashMap<String, Object>();
		param.put("groupId", memberTradeDetailInDTO.getGroupId());
		param.put("memberId", memberTradeDetailInDTO.getMemberId());
		param.put("transactionStatus", memberTradeDetailInDTO.getTransactionStatus());
		param.put("payType", memberTradeDetailInDTO.getPayType());
		param.put("transactionType", memberTradeDetailInDTO.getTransactionType());
		param.put("joinStart", memberTradeDetailInDTO.getJoinStart());
		param.put("joinEnd", memberTradeDetailInDTO.getJoinEnd());
		param.put("orderNo", memberTradeDetailInDTO.getOrderNo());

		// 还有订单号

		int sumCount = tradefflineMapper.queryTradeDetailCount(param);
		page.setTotalResult(sumCount);
		if (sumCount <= 0)
			return memberListOutDTO;

		param.put("limit", page.getShowCount());
		param.put("start", page.getShowCount() * (page.getCurrentPage() - 1));

		List<MemberTradeDetailOutDTO> tradeDetailList = tradefflineMapper.queryTradeDetailList(param);
		memberListOutDTO.setMemberTradeDeatilOutDTOList(tradeDetailList);
		return memberListOutDTO;
	}

	@Override
	public MemberConsumeOutDTO queryMemberConsumeData(MemberTradeDetailInDTO memberTradeDetailInDTO) {

		return memberMapper.queryMemberConsumeData(memberTradeDetailInDTO);
	}

	@Override
	public MemberListOutDTO queryMemberBonusList(MemberBonusLogInDTO memberBonusLogInDTO, Page page) {

		MemberListOutDTO memberListOutDTO = new MemberListOutDTO();

		Map<String, Object> param = new HashMap<String, Object>();
		param.put("groupId", memberBonusLogInDTO.getGroupId());
		param.put("memberId", memberBonusLogInDTO.getMemberId());
		param.put("adjustStatus", memberBonusLogInDTO.getAdjustStatus());
		param.put("sendType", memberBonusLogInDTO.getSendType());
		param.put("joinStart", memberBonusLogInDTO.getJoinStart());
		param.put("joinEnd", memberBonusLogInDTO.getJoinEnd());

		int sumCount = bonusSendLogMapper.queryBonusSendDetailCount(param);
		page.setTotalResult(sumCount);
		if (sumCount <= 0)
			return memberListOutDTO;

		param.put("limit", page.getShowCount());
		param.put("start", page.getShowCount() * (page.getCurrentPage() - 1));

		List<MemberBonusDetailOutDTO> memberBonusDetailOutDTOList = bonusSendLogMapper.queryBonusSendDetailList(param);
		memberListOutDTO.setMemberBonusDetailOutDTOList(memberBonusDetailOutDTOList);
		return memberListOutDTO;
	}

	/**
	 * 代理商后台门店
	 */
	public List<MemberOutDTO> getAgentMemberList(Long agentId, Long gradeId, String fromName, Integer wxsubStaus, Date joinStart, Date joinEnd, String name,
			Page page) {
		Map<String, Object> param = new HashMap<String, Object>();
		param.put("agentId", agentId);
		param.put("gradeId", gradeId);
		param.put("wxsubStaus", wxsubStaus);
		param.put("fromName", fromName);
		param.put("joinStart", joinStart);
		param.put("joinEnd", joinEnd);
		param.put("name", name);

		List<MemberOutDTO> result = new ArrayList<MemberOutDTO>();

		int sumCount = memberMapper.queryMemberListCount(param);
		page.setTotalResult(sumCount);
		if (sumCount <= 0)
			return null;

		param.put("limit", page.getShowCount());
		param.put("start", page.getShowCount() * (page.getCurrentPage() - 1));

		List<Member> memberList = memberMapper.queryMemberList(param);

		for (Member member : memberList) {
			MemberOutDTO memberOutDTO = new MemberOutDTO();


			memberOutDTO.setId(member.getId());
			memberOutDTO.setCardNo(member.getCardNo());
			memberOutDTO.setName(member.getName());
			memberOutDTO.setPhone(member.getPhone());
			memberOutDTO.setGradeId(member.getGradeId());
			memberOutDTO.setMemberGradeName(member.getMemberGradeName());
			memberOutDTO.setWxsubStaus(member.getWxsubStaus());
			memberOutDTO.setUpdateAmount(member.getUpdateAmount());
			memberOutDTO.setJoinDate(member.getGmtCreate());
			memberOutDTO.setWalletStatus(member.getWalletStatus());
			memberOutDTO.setFromType(member.getFromType());
			memberOutDTO.setFromName(member.getFromName());
			memberOutDTO.setFromId(member.getFromId());
			memberOutDTO.setFromMode(member.getFromMode());
			memberOutDTO.setIccardNo(member.getIccardNo());


			result.add(memberOutDTO);
		}

		return result;
	}

	public Member findAgentMemberById(Member member) {
		return memberMapper.findMemberById(member.getId());
	}

	@Override
	public Member findAgentPasswordById(Member member) {
		return memberMapper.queryPasswordById(member);
	}

	@Override
	public Member findAgentById(Member member) {
		return memberMapper.findById(member.getId());

	}

	@Override
	public Member findAgentMemberDetailById(Member member) {
		return memberMapper.findMemberDetailById(member.getId());
	}

	@Override
	public void updateAgentMemberLoginPassword(Member member) {

		memberMapper.updateByPrimaryKeySelective(member);

	}

	@Override
	public MemberListOutDTO queryAgentTradeDetail(MemberTradeDetailInDTO memberTradeDetailInDTO, Page page) throws Exception {
		MemberListOutDTO memberListOutDTO = new MemberListOutDTO();

		Map<String, Object> param = new HashMap<String, Object>();
		param.put("agentId", memberTradeDetailInDTO.getAgentId());
		param.put("memberId", memberTradeDetailInDTO.getMemberId());
		param.put("transactionStatus", memberTradeDetailInDTO.getTransactionStatus());
		param.put("payType", memberTradeDetailInDTO.getPayType());
		param.put("transactionType", memberTradeDetailInDTO.getTransactionType());
		param.put("orderNo", memberTradeDetailInDTO.getOrderNo());
		param.put("joinStart", memberTradeDetailInDTO.getJoinStart());
		param.put("joinEnd", memberTradeDetailInDTO.getJoinEnd());

		int sumCount = tradefflineMapper.queryShopTradeDetailCount(param);
		page.setTotalResult(sumCount);
		if (sumCount <= 0)
			return memberListOutDTO;

		param.put("limit", page.getShowCount());
		param.put("start", page.getShowCount() * (page.getCurrentPage() - 1));

		List<MemberTradeDetailOutDTO> tradeDetailList = tradefflineMapper.queryShopTradeDetailList(param);
		memberListOutDTO.setMemberTradeDeatilOutDTOList(tradeDetailList);
		return memberListOutDTO;
	}

	@Override
	public MemberConsumeOutDTO queryAgentMemberConsumeData(MemberTradeDetailInDTO memberTradeDetailInDTO) throws Exception {
		return memberMapper.queryAgentMemberConsumeData(memberTradeDetailInDTO);
	}

	/**
	 * 门店后台
	 */
	public List<MemberOutDTO> getShopMemberList(Long shopId, Long gradeId, String fromName, Integer wxsubStaus, Date joinStart, Date joinEnd, String name,
			Page page) {
		Map<String, Object> param = new HashMap<String, Object>();

		param.put("shopId", shopId);
		param.put("gradeId", gradeId);
		param.put("wxsubStaus", wxsubStaus);
		param.put("fromName", fromName);
		param.put("joinStart", joinStart);
		param.put("joinEnd", joinEnd);
		param.put("name", name);

		List<MemberOutDTO> result = new ArrayList<MemberOutDTO>();

		int sumCount = memberMapper.selectMemberShopListCount(param);
		page.setTotalResult(sumCount);
		if (sumCount <= 0)
			return null;

		param.put("limit", page.getShowCount());
		param.put("start", page.getShowCount() * (page.getCurrentPage() - 1));

		List<Member> memberList = memberMapper.selectMemberShopList(param);

		for (Member member : memberList) {
			MemberOutDTO memberOutDTO = new MemberOutDTO();

			memberOutDTO.setId(member.getId());
			memberOutDTO.setCardNo(member.getCardNo());
			memberOutDTO.setName(member.getName());
			memberOutDTO.setPhone(member.getPhone());
			memberOutDTO.setGradeId(member.getGradeId());
			memberOutDTO.setMemberGradeName(member.getMemberGradeName());
			memberOutDTO.setWxsubStaus(member.getWxsubStaus());
			memberOutDTO.setConsumeAmount(Long.parseLong(member.getConsumeAmount().toString()));
			memberOutDTO.setJoinDate(member.getGmtCreate());
			memberOutDTO.setWalletStatus(member.getWalletStatus());
			memberOutDTO.setFromType(member.getFromType());
			memberOutDTO.setFromName(member.getFromName());
			memberOutDTO.setFromId(member.getFromId());
			memberOutDTO.setFromMode(member.getFromMode());
			memberOutDTO.setIccardNo(member.getIccardNo());

			result.add(memberOutDTO);
		}

		return result;
	}

	@Override
	public Member findShopMemberDetailById(Member member) {
		return memberMapper.findShopMemberDetailById(member.getId());
	}

	@Override
	public MemberListOutDTO queryShopTradeDetail(MemberTradeDetailInDTO memberTradeDetailInDTO, Page page) throws Exception {
		MemberListOutDTO memberListOutDTO = new MemberListOutDTO();

		Map<String, Object> param = new HashMap<String, Object>();
		param.put("shopId", memberTradeDetailInDTO.getShopId());
		param.put("memberId", memberTradeDetailInDTO.getMemberId());
		param.put("transactionStatus", memberTradeDetailInDTO.getTransactionStatus());
		param.put("payType", memberTradeDetailInDTO.getPayType());
		param.put("transactionType", memberTradeDetailInDTO.getTransactionType());
		param.put("orderNo", memberTradeDetailInDTO.getOrderNo());
		param.put("joinStart", memberTradeDetailInDTO.getJoinStart());
		param.put("joinEnd", memberTradeDetailInDTO.getJoinEnd());

		int sumCount = tradefflineMapper.queryAgentTradeDetailCount(param);
		page.setTotalResult(sumCount);
		if (sumCount <= 0)
			return memberListOutDTO;

		param.put("limit", page.getShowCount());
		param.put("start", page.getShowCount() * (page.getCurrentPage() - 1));

		List<MemberTradeDetailOutDTO> tradeDetailList = tradefflineMapper.queryAgentTradeDetailList(param);
		memberListOutDTO.setMemberTradeDeatilOutDTOList(tradeDetailList);
		return memberListOutDTO;
	}

	@Override
	public MemberConsumeOutDTO queryShopMemberConsumeData(MemberTradeDetailInDTO memberTradeDetailInDTO) throws Exception {
		return memberMapper.queryShopMemberConsumeData(memberTradeDetailInDTO);
	}

	@Override
	public Member findByOpenId(String openid, Long groupId) throws Exception {
		return memberMapper.findMemberByopenid(openid, groupId);
	}

	/**
	 * 查询账户余额
	 */
	@Override
	public MemberOutDTO queryAmountOpenId(String openid, String groupId) throws ApplicationException {
		MemberOutDTO memberOutDTO = new MemberOutDTO();
		Member member = memberMapper.queryGroupOpenId(Long.valueOf(groupId), openid);
		if (member == null) {
			// 如果会员信息不存在 可能是pos机付款关注的 需要进行新开会员处理 但此时只能拿到会员openId
			Userbase userbase = new Userbase();
			userbase.setGroupId(Long.valueOf(groupId));
			userbase.setUserType(CommonEnum.UserType.User.getType());
			userbase.setBz("会员pos机关注微信");
			userbase.setGmtCreate(new Date());
			userbase.setGmtModified(new Date());
			userbase.setStatus(UserStatus.Normal.getType());
			userbaseMapper.insertKey(userbase);
			Member memberInfo = new Member();
			memberInfo.setAddress(null);
			memberInfo.setBirthday(null);
			memberInfo.setCardNo(DateUtil.getMonth() + Tools.getRandomNum(6));// 会员卡号
			memberInfo.setFromType(BizEnum.MemberDevelopeFrom.SelfRegister.getType());// 发展来源(枚举)
			memberInfo.setFromId(Long.valueOf(groupId)); // 发展来源id 门店id 大商户id
															// 会员id
			memberInfo.setFromName(BizEnum.MemberDevelopeFrom.SelfRegister.getName());// 发展来源名称
			memberInfo.setFromMode(BizEnum.MemberDevelopeMode.ScanQRcode.getType());
			memberInfo.setGmtCreate(new Date());
			memberInfo.setGmtModified(null);
//			MemberGrade memberGrade = memberGradeMapper.selectMemberGradeByGroupIdAndGradeName(Long.valueOf(groupId),
//					BizEnum.MemberGradeDefault.attention.getName());
			//取值第一个会员等级id
			  List<MemberGrade> memberGradeList=memberGradeMapper.selectGroupList(Long.valueOf(groupId));
			if (memberGradeList.size() >0) {
				memberInfo.setGradeId(memberGradeList.get(0).getId());// 会员等级
			} else {
				memberInfo.setGradeId(1L);// 会员等级
			}
			String CertNo = "000000000000000000";// 长度必须是18位
			String MobilePhone = "00000000000";
			memberInfo.setGroupId(Long.valueOf(groupId));
			memberInfo.setIdNo(CertNo);// 身份证号
			memberInfo.setName(null);
			memberInfo.setOpenid(openid);

			wxService.setWxMpConfigStorage(wxBaseService.getTokenByGroupId(Long.parseLong(groupId)));
			String lang = "zh_CN"; //语言
			try {
				WxMpUser user = wxService.getUserService().userInfo(openid,lang);
				//根据 unionid判断用户是否关注了   unionid不为空 代表为已关注
				if(Tools.notEmpty(user.getUnionId())){
					memberInfo.setWeixinName(this.emojiConverter.toAlias(user.getNickname()));
					memberInfo.setPicture(user.getHeadImgUrl());//图片
					memberInfo.setSex(user.getSexId()%2);
					memberInfo.setName(user.getNickname());
					memberInfo.setWxsubStaus(BizEnum.WebChatConcernStatus.Concerned.getType());
				}else{
					memberInfo.setWeixinName(null); 
					memberInfo.setPicture(null);//图片
					memberInfo.setSex(null);
					memberInfo.setName(null);
					memberInfo.setWxsubStaus(BizEnum.WebChatConcernStatus.UnConcern.getType());
				}
			} catch (WxErrorException e) {
				e.printStackTrace();
			}
			memberInfo.setPhone(MobilePhone);
			memberInfo.setStatus(1);// 会员状态(枚举)
			memberInfo.setTradePassword(null);// 交易密码
			memberInfo.setUserId(userbase.getId());
			memberInfo.setVirtualCard(null);// 虚拟卡号 对应支付平台userId
			memberInfo.setWalletGmtCreate(new Date());
			memberInfo.setWalletStatus(0);// 钱包状态(0:未开;1:开通)
			memberMapper.insertSelective(memberInfo);
			// 直接返回会员id出去
			memberOutDTO.setId(memberInfo.getId());
			return memberOutDTO;
		}else{
			//如果头像或者昵称为空 再次去拿去用户的头像等信息
			if(Tools.isEmpty(member.getWeixinName())||Tools.isEmpty(member.getPicture())){
				wxService.setWxMpConfigStorage(wxBaseService.getTokenByGroupId(Long.parseLong(groupId)));
				String lang = "zh_CN"; //语言
				try {
					WxMpUser user = wxService.getUserService().userInfo(openid,lang);
					//只有公众号关注了 才会有此字段
						if(Tools.notEmpty(user.getUnionId())){
							member.setWeixinName(this.emojiConverter.toAlias(user.getNickname()));
							member.setPicture(user.getHeadImgUrl());//图片
							member.setSex(user.getSexId()%2);
							member.setName(user.getNickname());
							member.setWxsubStaus(BizEnum.WebChatConcernStatus.Concerned.getType());
							memberMapper.updateByPrimaryKeySelective(member);
						  }
				} catch (WxErrorException e) {
					e.printStackTrace();
				}
				
			}
		}

		if (Tools.isEmpty(member.getVirtualCard())) {
			memberOutDTO.setId(member.getId());
			return memberOutDTO;
		}
		String payGroupCode = member.getPayGroupCode();// 支付平台大商户id
		
	//	Integer curBal = selectCurBal(userId, payGroupCode);
		
		Wallet wallet=walletService.selectwallet(member.getVirtualCard(), payGroupCode, member.getUserId());
		
		Integer count=wallet.getCanBalance()+wallet.getNocanBalance();
		
		RedpackageUser redpackageUser = redpackageUserMapper.packageUserCount(member.getId());
		if (redpackageUser != null) {
			memberOutDTO.setRedPacket(redpackageUser.getRedpackageId());
		} else {
			memberOutDTO.setRedPacket(0L);
		}
		memberOutDTO.setVirtualCard(member.getVirtualCard());
		memberOutDTO.setId(member.getId());
		memberOutDTO.setCurBal(count+"");
		return memberOutDTO;
	}


	/***
	 * 插入会员交易数据异步(并判断是否需要自动升级)
	 */
	@Override
	public int insertMemberTradeData(Long memberId, Integer amount, Integer bonusValue) throws Exception {
		int result = 0;
		if (memberId == null || memberId <= 0) {
			throw new ApplicationException(Rescode.FAIL, "memberId 不能为空！");
		}
		if (amount == null || amount < 0) {
			throw new ApplicationException(Rescode.FAIL, "amount 不能为空！");
		}

		if(bonusValue==null){
			bonusValue=0;
		}
		Member member = memberMapper.selectByPrimaryKey(memberId);
		member.setUpdateAmount(member.getUpdateAmount() == null ? 0 : member.getUpdateAmount());
		StatisMember statisMember = statisMemberMapper.selectByMemberId(memberId);

		Member memberUpdate = new Member();
		memberUpdate.setId(member.getId());
		memberUpdate.setUpdateAmount(amount + member.getUpdateAmount());
		logger.info ("插入会员交易数据异步(并判断是否需要自动升级)---------------------------------------------"); 
		StringBuffer sb = new StringBuffer();
		// 计算总金额
		if (statisMember != null) {// 统计信息已存在
			StatisMember statisMemberUpdate = new StatisMember();
			statisMemberUpdate.setId(statisMember.getId());
			statisMemberUpdate.setGmtModified(new Date());
			statisMemberUpdate.setConsumeNum(statisMember.getConsumeNum() + 1);// 记录数加1;
			statisMemberUpdate.setConsumeAmount(amount + statisMember.getConsumeAmount());// 金额相加;
			logger.debug("消费笔数"+statisMember.getConsumeNum() + 1+"消费金额"+amount + statisMember.getConsumeAmount());
			if(bonusValue>0) {
				statisMemberUpdate.setBonusNum(statisMember.getBonusNum() + 1);// 记录数加1;
				statisMemberUpdate.setBonusValue(bonusValue + statisMember.getBonusValue());// 金额相加;
			}
			statisMemberMapper.updateByPrimaryKeySelective(statisMemberUpdate);
			statisMemberUpdate.getConsumeAmount();

		} else { // 不存在
			StatisMember statisMemberInsert = new StatisMember();
			statisMemberInsert.setGmtCreate(new Date());
			statisMemberInsert.setGmtModified(new Date());
			statisMemberInsert.setMemberId(memberId);
			statisMemberInsert.setGroupId(member.getGroupId());
			statisMemberInsert.setConsumeNum(1);
			statisMemberInsert.setConsumeAmount(Long.parseLong(amount.toString()));
			if(bonusValue>0) {
				statisMemberInsert.setBonusNum(1);
				statisMemberInsert.setBonusValue(Long.parseLong(bonusValue.toString()));
			}
			statisMemberMapper.insert(statisMemberInsert);
		}

		// 根据金额查询会员升级等级信息
		MemberGrade memberGrade = memberGradeMapper.selectGradeIdByAmount(member.getGroupId(), memberUpdate.getUpdateAmount());
		// 需要升级
		if (memberGrade != null && (!memberGrade.getId().equals(member.getGradeId()))) {
			memberUpdate.setUpdateTime(new Date());
			memberUpdate.setGradeId(memberGrade.getId());
			logger.info(sb.append("会员id:").append(member.getId()).append(" 会员名:").append(member.getName()).append("由").append(member.getGradeId())
					.append("级升级到").append(memberGrade.getId()).toString());

			//立即赠送优惠券、积分、红包
			List<ActivityRoutine> activityRoutineList = activityRoutineMapper.selectByActivityType(ActivityEnum.RoutineActivityType.UpdateSend.getType());
			for(ActivityRoutine activityRoutine:activityRoutineList) {
				ActivityBase activityBase = activityBaseMapper.selectByRoutineId(activityRoutine.getActivityId());
                if(activityBase.getGroupId() == member.getGroupId()) {
                    //全部会员或等级会员一同处理
                    //if(activityRoutine.getMemberRiented() == ActivityEnum.MemberOriented.AllMember.getType()){
                    List<ActivityRoutineRule> activityRoutineRuleList = activityRoutineRuleMapper.selectValidRuleListByActivityId(activityRoutine.getActivityId());
                    for (ActivityRoutineRule activityRoutineRule : activityRoutineRuleList) {
                        if (activityRoutineRule.getSendType() == null)
                            activityRoutineRule.setSendType(ActivityEnum.ActivitySendType.NoSend.getType());
                        switch (ActivityEnum.ActivitySendType.fromType(activityRoutineRule.getSendType())) {
                            case RedPackage:
                                try {
                                    result = redPackageUserService.sendOneMemberRedPackage(member.getId(),
                                            activityRoutineRule.getRedpackageId(), activityBase.getId(), ActivityEnum.RedPackageGetType.ActivitySend.getType(), null);
                                } catch (Exception ae) {
                                    ae.printStackTrace();
                                    logger.error(ae);
                                }
                                break;
                            case Coupon:
                                try {
                                    result = couponUserService.sendOneMemberCoupon(member.getId(),
                                            activityRoutineRule.getCouponId(), activityBase.getId(), ActivityEnum.RedPackageGetType.ActivitySend.getType(), null);
                                } catch (Exception ae) {
                                    ae.printStackTrace();
                                    logger.error(ae);
                                }
                                break;
                            case Bonus:
                                try {
                                    BonusSendLog bonusSendLog = BonusSendLog.build(activityBase.getGroupId(), member.getId(), ActivityEnum.BonusSendType.UpdateSend.getType(),
                                            activityRoutineRule.getIntegral(), ActivityEnum.BonusSendStatus.Accounted.getType(), null, null, null, "会员升级送", activityBase.getId());
                                    result = bonusService.sendOneMemberBonus(bonusSendLog);
                                } catch (Exception e) {
                                    e.printStackTrace();
                                    logger.error(e);
                                }
                                break;

                            default:
                                break;
                        }
                    }
                }
			}
		}

		memberUpdate.setLastTradeTime(new Date());
		memberMapper.updateByPrimaryKeySelective(memberUpdate);
		return result;
	}

	/***
	 * 插入会员交易数据异步(并判断是否需要自动升级)
	 */
	@Override
	public int insertMemberTradeDataAsyn(final Long memberId, final Integer amount, final Integer bonusValue) throws Exception {
		exec.submit((new Runnable() {
			@Override
			public void run() {
				try {
					insertMemberTradeData(memberId, amount, bonusValue);
				} catch (Exception e) {
					logger.error(e);
					// e.printStackTrace();
				}
			}
		}));
		return 1;
	}

	/***
	 * 插入会员交易数据异步(并判断是否需要自动升级)
	 */
	@Override
	public int insertMemberTradeDataAsyn(final Long memberId, final Integer amount) throws Exception {
		return insertMemberTradeDataAsyn(memberId, amount, 0);
	}

	@Override
	public int insertMemberTradeDataAsyn(String thirdUserID, Integer amount) {
		Member member = memberMapper.selectByThirdUserId(thirdUserID);
		exec.submit((new Runnable() {
			@Override
			public void run() {
				try {
					insertMemberTradeData(member.getId(), amount, 0);
				} catch (Exception e) {
					logger.error(e);
					// e.printStackTrace();
				}
			}
		}));
		return 1;
	}

	@Override
	public YsObd queryOdbDetail(YsObd ysObd) throws Exception {

		return ysObdMapper.queryOdbDetail(ysObd);
	}

	@Override
	public MemberOutDTO addBalance(BalanceInDTO balanceInDTO,String rootHomeUrl) throws ApplicationException {
		MemberOutDTO memberOutDTO = new MemberOutDTO();
		Integer tranAmt = Integer.valueOf(balanceInDTO.getTranAmt()) * 100;
		Member member = memberMapper.queryGroup(balanceInDTO.getId());
		String orgOrderNum = DateUtils.getDateTimeString("yyyyMMddHHmmss");
		Date date = new Date();
		TradeOffline trade = new TradeOffline();
		trade.setGmtCreate(date);
		trade.setGmtModified(date);
		trade.setGroupId(member.getGroupId());
		trade.setOrderId(orgOrderNum);
		trade.setPayerId(member.getGroupId());// 付款者id号
		trade.setPayerName(member.getMerchantName());// 付款者姓名
		trade.setPayerType((byte) CommonEnum.UserType.User.getType());
		trade.setPayType((byte) BizEnum.PaymentType.Wallet.getType());// 支付方式
																		// 生成订单支付方式未知
		trade.setReceiverId(member.getId().toString());// 接收者id
		trade.setReceiverName(member.getName());// 接收者 此处以核销录入数据
		if(balanceInDTO.getCanDraw().equals("1")){
			trade.setTransactionType((byte) BizEnum.TransactionType.AddBalance.getType());// 交易类型
		}else{
			trade.setTransactionType((byte) BizEnum.TransactionType.NoAddBalance.getType());// 交易类型
		}
		trade.setSubType((byte) BizEnum.PaymentScene.Online.getType());// 支付场景
		trade.setOrderAmount(tranAmt); // 订单金额
		trade.setDiscountAmount(0);// 折扣金额
		trade.setRealAmount(tranAmt);// 实付金额
		trade.setTransactionStatus((byte) BizEnum.TransactionStatus.Success.getType());// 交易状态
		trade.setIsWallet(false);
		trade.setGoodType(null);// 商品类型(线上用) ？
		trade.setMemo(Tools.notEmpty(balanceInDTO.getRemark())?balanceInDTO.getRemark():"大商户修改余额");
		trade.setDetail(Tools.notEmpty(balanceInDTO.getRemark())?balanceInDTO.getRemark():"大商户修改余额");
		trade.setMerchantNo(null);// 商户号(对账用)
		trade.setTerminalNo(null);// 商户终端号
		trade.setPayAccount("");// 支付卡号
		trade.setScanOrganization(null);// 扫码付入网机构
		trade.setCrcodeStr(null);
		trade.setOldOrderId(null);
		trade.setDividableAmount(0);// 可分润金额
		trade.setAttachStatus(BizEnum.ProfitCalculateStatus.NoDeal.getType());
		trade.setPayOrderid(orgOrderNum);
		trade.setPayBakOrderid(null);
		trade.setInNetCompany(null);// 入网机构
		tradeOfflineMapper.insertSelective(trade);
		PayResult flag=walletService.updateUserLockedAmount(member.getVirtualCard(), member.getPayGroupCode(), member.getUserId(), tranAmt+"", balanceInDTO.getCanDraw(), 0,orgOrderNum);
		if (flag!=null) {
			// 增加余额成功
			memberOutDTO.setErrorCode(Rescode.SUCCESS, "处理成功");
			logger.info("--余额增加成功--");
			// 云流消息发送
			if (Tools.notEmpty(member.getThirdUserId())) {
				try {
					wxApiWalletServiceService.updatefinishSendMessage(orgOrderNum, UserAuthApi.MC_BLANCE_CHANGE);
				} catch (Exception e) {
					logger.info("--云流消息发送异常--");
				}
			}else if(Tools.notEmpty(member.getOpenid())){
				 //微信发送模板消息	
				try {
					templateMailSendService.sendTemplate(trade,  BizEnum.WebTemplateType.template13.getType(), trade.getPayerId(),
							trade.getGroupId(), BizEnum.PaymentType.WebChat.getType(),rootHomeUrl);
				} catch (Exception e) {
					logger.info ("模板消息发送失败"+e); 
				}
				
			}
			return memberOutDTO;
		} else {
			throw new ApplicationException(Rescode.FAIL, "余额变化失败");
		}

	}

	@Override
	public Member selectByOpenId(String openId) throws Exception {
		// TODO Auto-generated method stub
		return memberMapper.selectOpenId(openId, null);
	}

	@Override
	public int sendBonusOrRedOrCoupon(Long memberId, Long gradeId, Long groupId) {

		List<MemberGrade> memberGradeList=memberGradeMapper.selectGroupList(groupId);
		//立即赠送优惠券、积分、红包
		List<ActivityRoutine> activityRoutineList = activityRoutineMapper.selectByActivityType(ActivityEnum.RoutineActivityType.UpdateSend.getType());
		for(ActivityRoutine activityRoutine:activityRoutineList) {
			ActivityBase activityBase = activityBaseMapper.selectByRoutineId(activityRoutine.getActivityId());
			if (activityBase.getGroupId() == groupId) {
				//全部会员或等级会员一同处理
				if (activityRoutine.getMemberRiented() == ActivityEnum.MemberOriented.AllMember.getType()) {
					List<ActivityRoutineRule> activityRoutineRuleList = activityRoutineRuleMapper.selectValidRuleListByActivityId(activityRoutine.getActivityId());
					for (ActivityRoutineRule activityRoutineRule : activityRoutineRuleList) {
						if (activityRoutineRule.getSendType() == null)
							activityRoutineRule.setSendType(ActivityEnum.ActivitySendType.NoSend.getType());

						switch (ActivityEnum.ActivitySendType.fromType(activityRoutineRule.getSendType())) {
							case RedPackage:
								try {
									redPackageUserService.sendOneMemberRedPackage(memberId,
											activityRoutineRule.getRedpackageId(), activityBase.getId(), ActivityEnum.RedPackageGetType.ActivitySend.getType(), null);
								} catch ( Exception ae ) {
									ae.printStackTrace();
									logger.error(ae);
								}
								break;
							case Coupon:
								try {
									couponUserService.sendOneMemberCoupon(memberId,
											activityRoutineRule.getCouponId(), activityBase.getId(), ActivityEnum.RedPackageGetType.ActivitySend.getType(), null);
								} catch ( Exception ae ) {
									ae.printStackTrace();
									logger.error(ae);
								}
								break;
							case Bonus:
								try {
									//如果升级活动面对所有会员，和对应等级会员规则。
									if (activityRoutine.getMemberRiented() == ActivityEnum.MemberOriented.AllMember.getType()) {
										if (activityRoutineRule.getMemberGrade() == null) {
											BonusSendLog bonusSendLog = BonusSendLog.build(activityBase.getGroupId(), memberId, ActivityEnum.BonusSendType.UpdateSend.getType(),
													activityRoutineRule.getIntegral(), ActivityEnum.BonusSendStatus.Accounted.getType(), null, null, null, "会员升级送", activityBase.getId());
											bonusService.sendOneMemberBonus(bonusSendLog);
										}
									} else if (gradeId.equals(activityRoutineRule.getMemberGrade())) {
										BonusSendLog bonusSendLog = BonusSendLog.build(activityBase.getGroupId(), memberId, ActivityEnum.BonusSendType.UpdateSend.getType(),
												activityRoutineRule.getIntegral(), ActivityEnum.BonusSendStatus.Accounted.getType(), null, null, null, "会员升级送", activityBase.getId());
										bonusService.sendOneMemberBonus(bonusSendLog);
									}

								} catch ( Exception e ) {
									e.printStackTrace();
									logger.error(e);
								}
								break;
							default:
								break;
						}


					}
				}else{

						List<ActivityRoutineRule> activityRoutineRuleList = activityRoutineRuleMapper.selectValidRuleListByActivityId(activityRoutine.getActivityId());
						for (ActivityRoutineRule activityRoutineRule : activityRoutineRuleList) {
							if (memberGradeList.get(0).getId()==activityRoutineRule.getMemberGrade()) {
								if (activityRoutineRule.getSendType() == null)
									activityRoutineRule.setSendType(ActivityEnum.ActivitySendType.NoSend.getType());

								switch (ActivityEnum.ActivitySendType.fromType(activityRoutineRule.getSendType())) {
									case RedPackage:
										try {
											redPackageUserService.sendOneMemberRedPackage(memberId,
													activityRoutineRule.getRedpackageId(), activityBase.getId(), ActivityEnum.RedPackageGetType.ActivitySend.getType(), null);
										} catch ( Exception ae ) {
											ae.printStackTrace();
											logger.error(ae);
										}
										break;
									case Coupon:
										try {
											couponUserService.sendOneMemberCoupon(memberId,
													activityRoutineRule.getCouponId(), activityBase.getId(), ActivityEnum.RedPackageGetType.ActivitySend.getType(), null);
										} catch ( Exception ae ) {
											ae.printStackTrace();
											logger.error(ae);
										}
										break;
									case Bonus:
										try {
//如果升级活动面对所有会员，和对应等级会员规则。
											if (activityRoutine.getMemberRiented() == ActivityEnum.MemberOriented.AllMember.getType()) {
												if (activityRoutineRule.getMemberGrade() == null) {
													BonusSendLog bonusSendLog = BonusSendLog.build(activityBase.getGroupId(), memberId, ActivityEnum.BonusSendType.UpdateSend.getType(),
															activityRoutineRule.getIntegral(), ActivityEnum.BonusSendStatus.Accounted.getType(), null, null, null, "会员升级送", activityBase.getId());
													bonusService.sendOneMemberBonus(bonusSendLog);
												}
											} else if (gradeId.equals(activityRoutineRule.getMemberGrade())) {
												BonusSendLog bonusSendLog = BonusSendLog.build(activityBase.getGroupId(), memberId, ActivityEnum.BonusSendType.UpdateSend.getType(),
														activityRoutineRule.getIntegral(), ActivityEnum.BonusSendStatus.Accounted.getType(), null, null, null, "会员升级送", activityBase.getId());
												bonusService.sendOneMemberBonus(bonusSendLog);
											}

										} catch ( Exception e ) {
											e.printStackTrace();
											logger.error(e);
										}
										break;
									default:
										break;
								}
							}

					}
				}
			}

		}


		return 1;
	}

	@Override
	public int updateMemberFirstTradeSend(Long id,Long memberId, Long groupId, Integer Amount) throws Exception {
		int result =0;


		Member member = memberMapper.selectByPrimaryKey(memberId);
		if(member!=null && member.getFromType()!=null && member.getFromType()==BizEnum.MemberDevelopeFrom.UserDevelope.getType()) {

			//判断会员是不是第一次消费
			int count = tradeOfflineMapper.queryTradeCount(memberId, groupId);
			if (count == 1) {//第一次消费

//				List<ActivityRoutineRegister> activityRoutineList = activityRoutineRegisterMapper.selectByActivityTypeAndGroupId(ActivityEnum.RoutineActivityType.InviteRegistration.getType(),groupId);
//				for (ActivityRoutineRegister activityRoutineRegister : activityRoutineList) {
				ActivityRoutineRegister activityRoutineRegister = activityRoutineRegisterMapper.selectRegisterActivityDataByGroupId(groupId);
				if (Amount >= activityRoutineRegister.getFirstInviterFullAmount()) {
					ActivityBase activityBase = activityBaseMapper.selectByRoutineId(activityRoutineRegister.getActivityId());

					if (activityRoutineRegister.getFirstInviterTradeSendType() == null)
						activityRoutineRegister.setFirstInviterTradeSendType(ActivityEnum.ActivitySendType.NoSend.getType());
					switch (ActivityEnum.ActivitySendType.fromType(activityRoutineRegister.getFirstInviterTradeSendType())) {
						case RedPackage:
							try {
								result = redPackageUserService.sendOneMemberRedPackage(member.getFromId(), activityRoutineRegister.getFirstInviterRedpackageId(),
										activityBase.getId(),ActivityEnum.RedPackageGetType.ActivitySend.getType(), null);

								if(result !=1){
									Member member1 = new Member();
									member1.setId(member.getFromId());
									member1.setGmtModified(new Date());
									if(result ==-1){
										member1.setFirstTradeMemo("红包已结束");
									}else if(result ==-2){
										member1.setFirstTradeMemo("红包已领完");
									}else if(result ==-3){
										member1.setFirstTradeMemo("过了结束领取时间");
									}else if(result ==-4){
										member1.setFirstTradeMemo("超过最大领取张数");
									}
									memberMapper.updateByPrimaryKeySelective(member1);
								}


							} catch (Exception ae) {
								ae.printStackTrace();
								logger.error(ae);
							}
							break;
						case Coupon:
							try {
								result = couponUserService.sendOneMemberCoupon(member.getFromId(), activityRoutineRegister.getFirstInviterCouponId(),
										activityBase.getId(),ActivityEnum.RedPackageGetType.ActivitySend.getType(), null, null);

										if(result !=1){
											Member member1 = new Member();
											member1.setId(member.getFromId());
											member1.setGmtModified(new Date());
											if(result ==-1){
												member1.setFirstTradeMemo("优惠券已经结束");
											}else if(result ==-2){
												member1.setFirstTradeMemo("优惠券已经领取完成");
											}else if(result ==-3){
												member1.setFirstTradeMemo("优惠券已经过期");
											}else if(result ==-4){
												member1.setFirstTradeMemo("过了有效结束时间");
											}else if(result ==-5){
												member1.setFirstTradeMemo("超过最大领取张数");
											}
											memberMapper.updateByPrimaryKeySelective(member1);

											System.out.print("开始----------------------");
										}
									} catch (Exception ae) {
								ae.printStackTrace();
								logger.error(ae);
							}
							break;
						case Bonus:
							try {
								BonusSendLog bonusSendLog = BonusSendLog.build(activityBase.getGroupId(), member.getFromId(), ActivityEnum.BonusSendType.routineActivityRegister.getType(),
										activityRoutineRegister.getFirstInviterIntegral().intValue(), ActivityEnum.BonusSendStatus.Accounted.getType(), null, null, null, "会员首次消费送", activityBase.getId());
								result = bonusService.sendOneMemberBonus(bonusSendLog);


								System.out.print("开始----------------------");

							} catch (Exception e) {
								e.printStackTrace();
								logger.error(e);
							}
							break;
						case Cash:
							try {

								logger.info("首次消费去推荐人新增记录");
								Integer firstInviterAmount = activityRoutineRegister.getFirstInviterAmount();
								String orderId=UtilFun.createOrderNum();
								Member member2 = memberMapper.selectByPrimaryKey(member.getFromId());
								Group group = groupMapper.selectByPrimaryKey(groupId);
								TradeOffline tradeOffline = new TradeOffline();
								tradeOffline.setRelatedTradeOfflineId(id);
								tradeOffline.setGmtCreate(new Date());
								tradeOffline.setGmtModified(new Date());
								tradeOffline.setGroupId(groupId);
								tradeOffline.setOrderId(orderId);
								tradeOffline.setReceiverId(member2.getId().toString());
								tradeOffline.setPayerId(groupId);
								tradeOffline.setPayerName(group.getMerchantName());
								tradeOffline.setPayType((byte)BizEnum.PaymentType.Wallet.getType());
								tradeOffline.setReceiverName(member2.getName());
								tradeOffline.setRelatedActivityId(activityBase.getId());
								tradeOffline.setTransactionStatus((byte)1);
								tradeOffline.setTransactionType((byte)BizEnum.TransactionType.ConsumptionBackCash.getType());
								tradeOffline.setIsWallet(true);
								tradeOffline.setMemo("首次消费返现");
								tradeOffline.setOrderAmount(activityRoutineRegister.getFirstInviterAmount());
								tradeOffline.setRealAmount(activityRoutineRegister.getFirstInviterAmount());
								tradeOfflineMapper.insertSelective(tradeOffline);
								logger.info("首次消费去推荐人更新钱包信息");
								walletService.updateLockedAmount(member2.getId().toString(), "1", firstInviterAmount.toString(), "0", 0,orderId);
								System.out.print("开始----------------------");

							} catch (Exception e) {
								e.printStackTrace();
								logger.error(e);
							}
							break;
						default:
							break;
					}

				}
			}
		}
//		}


		return result;
	}


	@Override
	public Member selectMemberByPhone(Member memberIn) {
		// TODO Auto-generated method stub
		
		if(memberIn!=null){
			Member member=memberMapper.selectMemberByPhone(memberIn);
			if(member!=null){
				return member;
			}
		}
			return null;
	}

	@Override
	public int updateStatisMemberInfo(Long memberId, Integer realAmount) {
		logger.info("==============退款金额"+realAmount);

		int result =0;
		memberMapper.updateMemberUpdateAmount(memberId,realAmount);

		result = statisMemberMapper.updateMemberCostomerInfo(memberId,realAmount);

		//根据会员ID查找到会员的等级信息
		Member memberupdateTemp = memberMapper.selectByPrimaryKey(memberId);
		logger.info("==============会员升级金额"+memberupdateTemp.getUpdateAmount());

		//根据渠道ID和会员消费总额，查询到会员等级降级的等级ID
		MemberGrade memberGrade = memberGradeMapper.selectDownGradeIdByAmount(memberupdateTemp.getGroupId(), memberupdateTemp.getUpdateAmount());
		//如果该会员当前的等级ID不等于其消费总额该拥有的等级，则判断为需要降级，进行降级操作
		if(memberGrade != null && (!memberupdateTemp.getGradeId().equals(memberGrade.getId()))){
			Member memberUpdate = new Member();

			//如果查询到的会员晋级金额为0，就默认将该会员修改为关注会员
			if(memberGrade.getUpdateAmount().equals(0)){
			    MemberGrade memberGradeTemp = new MemberGrade();
			    memberGradeTemp.setMerchantId(memberupdateTemp.getGroupId());
			    memberGradeTemp.setName(BizEnum.MemberGradeDefault.attention.getName());
                MemberGrade getMemberGradeId=memberGradeMapper.selectMemberGradeByGroupIdAndGradeName(memberGradeTemp);
                memberUpdate.setGradeId(getMemberGradeId.getId());
            }else{
				memberUpdate.setGradeId(memberGrade.getId());
			}
			memberUpdate.setId(memberupdateTemp.getId());
			memberUpdate.setUpdateTime(new Date());
			logger.info("会员ID："+memberupdateTemp.getId()+" 会员名："+memberupdateTemp.getName()+" 由："+memberupdateTemp.getGradeId()+" 降级到："+memberGrade.getId());
			memberMapper.updateByPrimaryKeySelective(memberUpdate);

		}

		return result;
	}

	@Override
	public Boolean updatequeryMemberBanal(String virtualCard, String payGroupCode, Long userId, Integer tranAmt) throws ApplicationException {
		Wallet wallet=walletMapper.selectByUserId(userId);
		if(wallet==null){
			PayBalanceResult payResult =getBalance(virtualCard, payGroupCode,false);
			Integer curBalA=Integer.valueOf(payResult.getCurBal());
			Integer curBalB=Integer.valueOf(payResult.getCurBalB());

			if((curBalA + curBalB)<tranAmt){
				return false;
			}
		}else{
			Integer BalanceA=wallet.getCanBalance();
			Integer BalanceB=wallet.getNocanBalance();
			if((BalanceA + BalanceB)<tranAmt){
				return false;
			}
		}
		return true;
	}
	/**
	 * 余额查询
	 * @param virtualCard  用户编号
	 * @param payGroupCode 机构号
	 * @return
	 * @throws ApplicationException
	 */
	public static PayBalanceResult  getBalance(String virtualCard,String payGroupCode,boolean isMerchant) throws ApplicationException{
		SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyyMMdd");
		String str = simpleDateFormat.format(new Date());
		String orgTranDateTime = str;
		String SysTraceNum = StringUtil.getRandNumberStr(12);// 交易流水号12位
		PayBalanceQuery payBalanceQuery = PayBalanceQuery.initialize(virtualCard, payGroupCode, SysTraceNum, orgTranDateTime, UtilFun.createOrderNum());
		PayBalanceResult payResult = IPayAPI.accountBalanceQuery(payBalanceQuery, isMerchant);
		if (!PayBalanceResult.SUCCESS.equals(payResult.getRespCode())) {
			throw new ApplicationException(payResult.getMsgTxt());
		}
		return payResult;
	}

	/**
	 * 添加会员信息
	 * @return
	 */
	public Long addMemberInfo(String groupId, String openid, String memberid) {
		// 如果会员信息不存在 可能是pos机付款关注的 需要进行新开会员处理 但此时只能拿到会员openId
		Userbase userbase = new Userbase();
		userbase.setGroupId(Long.valueOf(groupId));
		userbase.setUserType(CommonEnum.UserType.User.getType());
		userbase.setBz("关注分享商品");
		userbase.setGmtCreate(new Date());
		userbase.setGmtModified(new Date());
		userbase.setStatus(UserStatus.Normal.getType());
		userbaseMapper.insertKey(userbase);
		Member memberInfo = new Member();
		memberInfo.setAddress(null);
		memberInfo.setBirthday(null);
		memberInfo.setCardNo(DateUtil.getMonth() + Tools.getRandomNum(6));// 会员卡号
		memberInfo.setFromType(BizEnum.MemberDevelopeFrom.UserDevelope.getType());// 发展来源(枚举)
		memberInfo.setFromId(Long.valueOf(memberid)); // 发展来源id 门店id 大商户id
		// 会员id
		memberInfo.setFromName(BizEnum.MemberDevelopeFrom.UserDevelope.getName());// 发展来源名称
		memberInfo.setFromMode(BizEnum.MemberDevelopeMode.ConcernedWeChat.getType());
		memberInfo.setGmtCreate(new Date());
		memberInfo.setGmtModified(null);
//			MemberGrade memberGrade = memberGradeMapper.selectMemberGradeByGroupIdAndGradeName(Long.valueOf(groupId),
//					BizEnum.MemberGradeDefault.attention.getName());
		//取值第一个会员等级id
		List<MemberGrade> memberGradeList=memberGradeMapper.selectGroupList(Long.valueOf(groupId));
		if (memberGradeList.size() >0) {
			memberInfo.setGradeId(memberGradeList.get(0).getId());// 会员等级
		} else {
			memberInfo.setGradeId(1L);// 会员等级
		}
		String CertNo = "000000000000000000";// 长度必须是18位
		String MobilePhone = "00000000000";
		memberInfo.setGroupId(Long.valueOf(groupId));
		memberInfo.setIdNo(CertNo);// 身份证号
		memberInfo.setName(null);
		memberInfo.setOpenid(openid);

		wxService.setWxMpConfigStorage(wxBaseService.getTokenByGroupId(Long.parseLong(groupId)));
		String lang = "zh_CN"; //语言
		try {
			WxMpUser user = wxService.getUserService().userInfo(openid,lang);
			//根据 unionid判断用户是否关注了   unionid不为空 代表为已关注
			if(Tools.notEmpty(user.getUnionId())){
				memberInfo.setWeixinName(this.emojiConverter.toAlias(user.getNickname()));
				memberInfo.setPicture(user.getHeadImgUrl());//图片
				memberInfo.setSex(user.getSexId()%2);
				memberInfo.setName(user.getNickname());
				memberInfo.setWxsubStaus(BizEnum.WebChatConcernStatus.Concerned.getType());
			}else{
				memberInfo.setWeixinName(null);
				memberInfo.setPicture(null);//图片
				memberInfo.setSex(null);
				memberInfo.setName(null);
				memberInfo.setWxsubStaus(BizEnum.WebChatConcernStatus.UnConcern.getType());
			}
		} catch (WxErrorException e) {
			e.printStackTrace();
		}
		memberInfo.setPhone(MobilePhone);
		memberInfo.setStatus(1);// 会员状态(枚举)
		memberInfo.setTradePassword(null);// 交易密码
		memberInfo.setUserId(userbase.getId());
		memberInfo.setVirtualCard(null);// 虚拟卡号 对应支付平台userId
		memberInfo.setWalletGmtCreate(new Date());
		memberInfo.setWalletStatus(0);// 钱包状态(0:未开;1:开通)
		memberMapper.insertSelective(memberInfo);
		// 直接返回会员id出去
		return memberInfo.getId();
	}
}